﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using SharedComponents;
using System.ComponentModel;

namespace OurLeague.Object
{
    public class Match
    {
        #region Fields

        Referee _referee;        
        LineUp _localLineUp;        
        LineUp _guestLineUp;
        Dayweek _dayweek;
        String _id;       
        String _result;
        bool _played;

        public static List<Match> Matches = new List<Match>();

        #endregion

        #region Constructors

        public Match() { }

        #endregion

        #region Public Methods

        public void save()
        {
            LocalLineUp.save();
            GuestLineUp.save();
            MySqlRecord updateRecord = new MySqlRecord();

            updateRecord["fkLineUpId1"] = LocalLineUp.Id;
            updateRecord["fkLineUpId2"] = GuestLineUp.Id;
            updateRecord["fkDayId"] = Dayweek.Id;
            updateRecord["fkRefereeId"] = Referee.Id;

            if (!Matches.Exists(m => m.Id == Id))
            {
                Matches.Add(this);
                Id = MySqlQueryHelper.saveQuery(MySqlManager.Connection, "Matches", null, updateRecord).ToString();

                return;
            }

            MySqlQueryHelper.saveQuery(MySqlManager.Connection, "Matches", "matchId=" + Id, updateRecord);  
        }

        public void delete()
        {
            delete(true);
        }

        public int scoredGoals()
        {
            return getGoalNumber(LocalLineUp);
        }

        public int concededGoals()
        {
            return getGoalNumber(GuestLineUp);
        }

        public String getResult(Match match)
        {
            int llups = getGoalNumber(LocalLineUp);
            int glups = getGoalNumber(GuestLineUp);

            return llups == glups && llups == 0 ? "--" : llups + " - " + glups;
        }

        public int getGoalNumber(LineUp lineup)
        {
            return Event.Events.Where(e => e.Player.TeamId == lineup.TeamId && e.Type == 1 && e.MatchId == Id).ToList().Count;
        }

        /*
        public void view()
        {

        }

        public void update(String a)
        { }

        public bool findMatch(String a)
        {
            return false;
        }

        public int minutesPlayed(String playerId)
        {
            return 0;
        }

        public bool play(String a)
        {
            return false;
        }

        public void home(String a)
        { }

        public void localFormation(List<Player> a, List<Player> b, String c)
        { }

        public void guestFormation(List<Player> a, List<Player> b, String c)
        { }

        public void addEvent(String a, int b, String c)
        { }

        public void editEvent(String a, String b, int c, String d)
        { }

        public void deleteEvent(String idEvent)
        { }
        */
        #endregion

        #region Private Methods

        private void delete(bool removeOnDB)
        {
            if (removeOnDB)
                MySqlQueryHelper.deleteQuery(MySqlManager.Connection, "Matches", "matchId", new String[] { Id });

            Matches.Remove(this);
            Event.removeAll(this);
            LineUp.removeAll(this);
        }

        #endregion

        #region Static Methods

        private static Match addNewMatch(MySqlRecord matchRecord)
        {
            Match match = new Match();

            match.Id = matchRecord["matchId"].ToString();
            match.Played = (bool)(matchRecord["played"]);
            match.Dayweek = Dayweek.load(matchRecord["fkDayId"].ToString());
            match.LocalLineUp = LineUp.load(matchRecord["fklineUpId1"].ToString());
            match.GuestLineUp = LineUp.load(matchRecord["fklineUpId2"].ToString());
            match.Referee = Referee.load(matchRecord["fkRefereeId"].ToString());
            match.Result = "PlaceHolder"; ;

            Matches.Add(match);

            return match;
        }

        public static void removeAll(Dayweek dw)
        {
            if (Dayweek.Dayweeks.Contains(dw))
                return;
            
            // Questi cicli vecchio stile son bellissimi! :**
            int i = 0;
            while (i < Matches.Count)
            {
                if (Matches[i].Dayweek == dw)
                {
                    Matches[i].delete(false);
                    continue;
                }

                i++;
            }
        }

        public static void loadAll()
        {
            loadAll(null);
        }

        public static List<Match> loadAll(String idDayweek)
        {
            MySqlRecordset queryResult = MySqlQueryHelper.selectQuery(MySqlManager.Connection, "Matches", null, (idDayweek != null) ? "matchId='" + idDayweek + "'" : null);
            
            foreach (MySqlRecord matchRecord in queryResult)
            {
                if (!Matches.Exists(m => m.Id == matchRecord["matchId"].ToString()))
                    addNewMatch(matchRecord);
            }

            if (idDayweek != null)
                return Matches.Where(m => m.Dayweek.Id == idDayweek).ToList();

            return null;
        }

        public static Referee getRandomReferee(String dayweekId)
        {
            loadAll(dayweekId);

            String sql_filter = "TRUE";
            List<Match> matchesDayweek = Matches.FindAll(m => m.Dayweek.Id == dayweekId);
            for(int i = 0; i < matchesDayweek.Count(); i++)
                sql_filter += " AND refereeId <> " + matchesDayweek[i].Referee.Id;

            MySqlRecordset queryResult = MySqlQueryHelper.selectQuery(MySqlManager.Connection, "Referees", new String[] {"refereeId"}, sql_filter + " ORDER BY RAND() LIMIT 1");

            if (queryResult.Count == 0)
                return null;

            return Referee.load(queryResult[0]["refereeId"].ToString());
        }

        public static Match load(String idMatch)
        {
            Match match = Matches.Find(m => m._id == idMatch);
            
            if (match == null)
            {
                var matchRecord = MySqlQueryHelper.selectQuery(MySqlManager.Connection, "Matches", null, "matchId='" + idMatch + "'");
                match = addNewMatch(matchRecord[0]);
            }

            return match;
        }

        public static int goalScored(String teamId)
        {
            //var 
            return 0;
        }

        #endregion

        #region Properties

        public Referee Referee
        {
            get { return _referee; }
            set { _referee = value; }
        }

        public LineUp GuestLineUp
        {
            get { return _guestLineUp; }
            set { _guestLineUp = value; }
        }

        public Dayweek Dayweek
        {
            get { return _dayweek; }
            set { _dayweek = value; }
        }

        public LineUp LocalLineUp
        {
            get { return _localLineUp; }
            set { _localLineUp = value; }
        }

        public String Id
        {
            get { return _id; }
            set { _id = value; }
        }

        public String Teams
        {
            get { return _localLineUp.TeamName + "-" + _guestLineUp.TeamName; }
        }

        public String Result
        {
            get { return getResult(this); }
            set { _result = value; }
        }

        public bool Played
        {
            get { return _played; }
            set { _played = value; }
        }

        #endregion
    }
}
